package com.fanbai.score.common.http;

import android.content.Context;
import android.content.Intent;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;

import com.fanbai.score.common.Utils.JsonUtils;
import com.fanbai.score.common.Utils.OtherUtils;
import com.fanbai.score.common.Utils.SPUtils;
import com.fanbai.score.common.Utils.log.YD_Log;
import com.zhy.http.okhttp.OkHttpUtils;
import com.zhy.http.okhttp.callback.FileCallBack;
import com.zhy.http.okhttp.callback.StringCallback;

import java.io.File;
import java.io.IOException;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import okhttp3.Call;

public class HttpUtils {

    /**
     * 异常状态：没有网络
     */
    public static final String STATE_NO_NET = "STATE_NO_NET";

    public static final IOException noNetException = new IOException("网络趴了，还没爬起来");
    /**
     * 异常状态：错误
     */
    public static final String STATE_ERROR = "STATE_ERROR";

    /**
     * get方式请求Json数据（ret、msg、body）,并封装为bean
     *
     * @param ctx      上下文，只接受Activity或Application上下文
     * @param url
     * @param callBack
     */
    public static void get(final Context ctx, String url, final BeanCallBack callBack) {
        if (!haveNet(ctx)) {
            if (callBack != null)
                callBack.onError(STATE_NO_NET, noNetException);
            return;
        }
        YD_Log.writeLog(url);
        OkHttpUtils.get().url(url).build().execute(new StringCallback() {
            @Override
            public void onResponse(String json, int id) {
                YD_Log.writeLog(json);
                String msg = JsonUtils.getString(json, "msg");
                String body = JsonUtils.getString(json, "body");
                int ret = JsonUtils.getInt(json, "retno");
                switch (ret) {
                    case 0:
                        // 服务器返回成功json信息
                        if (callBack != null)
                            callBack.onSuccess(ret + "", msg, body);
                        break;
                    case Integer.MIN_VALUE:
                        // json解析失败
                        if (callBack != null)
                            callBack.onFailure(ret + "", "数据解析失败", json);
                        break;
                    case -2:
                        // token超时
                        // 删除信息
                        SPUtils.removeUserInfo(ctx);
                        // 切换到登录窗口
//                        Intent intent = new Intent(ctx, Login_Activity.class);
//                        ctx.startActivity(intent);
                        // 服务器返回失败json信息
                        if (callBack != null)
                            callBack.onFailure(ret + "", "登录信息已过期，请重新登录", body);
                        break;
                    case -1:
                        // 服务器返回失败json信息
                        if (callBack != null)
                            callBack.onFailure(ret + "", msg, body);
                        break;
                    default:
                        if (callBack != null)
                            callBack.onFailure(ret + "", msg, body);
                        break;
                }
            }

            @Override
            public void onError(Call call, Exception e, int id) {
                YD_Log.e("http", e.getMessage());
                YD_Log.writeLog("e", "报错：" + e.getMessage());
                if (callBack != null)
                    callBack.onError(STATE_ERROR, e);
            }
        });
    }

    /**
     * post请求Json数据（ret、msg、body）,并封装为bean
     *
     * @param ctx      上下文，只接受Activity或Application上下文
     * @param url
     * @param params
     * @param callBack
     */
    public static void post(final Context ctx, final String url, Map<String, String> params,
                            final BeanCallBack callBack) {
        if (!haveNet(ctx)) {
            if (callBack != null)
                callBack.onError(STATE_NO_NET, noNetException);
            return;
        }
        // 检查链接传参
        String urlWhole = null;
        for (Map.Entry<String, String> entry : params.entrySet()) {
            if (urlWhole == null) {
                urlWhole = url + "?" + entry.getKey() + "=" + entry.getValue();
            } else {
                urlWhole += "&" + entry.getKey() + "=" + entry.getValue();
            }
        }
        YD_Log.writeLog(urlWhole);
        // 网络连接
        OkHttpUtils.post().url(url).params(params).build().execute(new StringCallback() {
            @Override
            public void onResponse(String json, int arg1) {
                YD_Log.writeLog(json);
                String msg = "出错了，请稍后再试";
                try {
                    msg = JsonUtils.getString(json, "msg");
                } catch (Exception e) {
                    e.printStackTrace();
                }
                String body = JsonUtils.getString(json, "result");
                int ret = JsonUtils.getInt(json, "retno");
                switch (ret) {
                    case 0:
                        // 服务器返回成功json信息
                        if (callBack != null)
                            YD_Log.e("返回信息："+body);
                            callBack.onSuccess(ret + "", msg, body);
                        break;
                    case Integer.MIN_VALUE:
                        if (callBack != null)
                            callBack.onFailure(ret + "", "数据解析失败", json);
                        break;
                    case 1:
                        if (callBack != null)
                            callBack.onFailure(ret + "", ""+ msg, json);
                        break;
                    case 2:
                        if (callBack != null)
                            callBack.onFailure(ret + "", ""+ msg, json);
                        break;
                    case 60:
                    case 80:
                        if (callBack != null)
                            callBack.onFailure(ret + "", ""+ msg, json);
                        break;
                    case 65:
                        if (callBack != null)
                            callBack.onFailure(ret + "", ""+ msg, json);
                        break;
                    case 70:
                        if (callBack != null)
                            callBack.onFailure(ret + "", ""+ msg, json);
                        break;
                    case 75:
                        if (callBack != null)
                            callBack.onFailure(ret + "", ""+ msg, json);
                        break;
                    case 100:

                        break;
                    /*case -2:
                        // token超时
                        // 删除信息
                        SPUtils.removeUserInfo(ctx);
                        // 切换到登录窗口(退出登录功能，不跳转)
                        if (!url.contains("/account/logout.jspx")) {
                            Intent intent = new Intent(ctx, Login_Activity.class);
                            ctx.startActivity(intent);
                        }
                        if (callBack != null)
                            callBack.onFailure(ret + "", "登录信息已过期，请重新登录", body);
                        break;
                    case -1:
                        // 服务器返回失败json信息
                        if (callBack != null)
                            callBack.onFailure(ret + "", msg, body);
                        break;*/
                    default:
                        if (callBack != null)
                            callBack.onFailure(ret + "", msg, body);
                        break;
                }
            }

            @Override
            public void onError(Call arg0, Exception e, int arg2) {
                YD_Log.e("http", e.getMessage());
                YD_Log.writeLog("e", "报错：" + e.getMessage());
                if (callBack != null)
                    callBack.onError(STATE_ERROR, e);
            }
        });
    }

    /**
     * 请求Json并封装为Bean时的回调接口
     *
     * @author Cong
     */
    public interface BeanCallBack {
        /**
         * 请求成功后返回json主体
         *
         * @param body 可直接编译bean的主体
         */
        void onSuccess(String ret, String msg, String body);

        /**
         * 请求数据失败后，返回json主体
         *
         * @param body
         */
        void onFailure(String ret, String msg, String body);

        /**
         * 请求网络连接失败
         *
         * @param e 错误信息
         */
        void onError(String code, Exception e);
    }

    /**
     * 下载文件
     *
     * @param url
     * @param fileDir
     * @param fileName
     */
    public static void download(final Context ctx, String url, String fileDir, String fileName,
                                final DownloadCallBack callBack) {
        OkHttpUtils.get().url(url).build().execute(new FileCallBack(fileDir, fileName) {
            @Override
            public void inProgress(float progress, long total, int id) {
                if (callBack != null)
                    callBack.inProgress(progress, total);
            }

            @Override
            public void onResponse(File file, int id) {
                if (callBack != null)
                    callBack.onResponse(file);
            }

            @Override
            public void onError(Call call, Exception e, int id) {
                if (callBack != null)
                    callBack.onError(e);
            }
        });
    }

    /**
     * 下载回调
     *
     * @author Cong
     */
    public interface DownloadCallBack {
        /**
         * 下载过程中循环调用
         *
         * @param progress 已下载的百分比？
         * @param total    总大小
         */
        void inProgress(float progress, long total);

        /**
         * 下载完成，响应结束
         *
         * @param file
         */
        void onResponse(File file);

        /**
         * 连接出错
         *
         * @param e
         */
        void onError(Exception e);
    }

    /**
     * 上传文件
     *
     * @param ctx
     * @param url      上传url
     * @param file     上传的文件
     * @param params
     * @param callBack
     */
    public static void upload(final Context ctx, String url, final File file, Map<String, String> params,
                              final UploadCallBack callBack) {
        if (!haveNet(ctx)) {
            if (callBack != null)
                callBack.onError(STATE_NO_NET, noNetException);
            return;
        }
        HashMap<String, String> headers = new HashMap<String, String>();
        headers.put("Connection", "Keep-Alive");
        headers.put("Charset", "UTF-8");
        headers.put("Content-Type", "multipart/form-data;boundary=--------");
        YD_Log.writeLog(url + "|" + file.getName());
        OkHttpUtils.post().addFile("userlogo", file.getName(), file).url(url).params(params).headers(headers).build()
                .execute(new StringCallback() {
                    @Override
                    public void inProgress(float progress, long total, int id) {
                        if (callBack != null)
                            callBack.inProgress(progress, total);
                    }

                    @Override
                    public void onResponse(String json, int arg1) {
                        YD_Log.writeLog(json);
                        String msg = JsonUtils.getString(json, "msg");
                        String body = JsonUtils.getString(json, "result");
                        switch (JsonUtils.getInt(json, "retno")) {
                            case Integer.MIN_VALUE:// json解析失败
                                if (callBack != null)
                                    callBack.onFailure("本地解析数据失败", json);
                                break;
                            case -2:
                                // token超时
                               // 删除信息
                                SPUtils.removeUserInfo(ctx);
                                // 切换到登录窗口
//                                Intent intent = new Intent(ctx, Login_Activity.class);
//                                ctx.startActivity(intent);
                                if (callBack != null)
                                    callBack.onFailure("登录信息已过期，请重新登录", body);
                                break;
                            case 1:
                                // 服务器返回失败json信息
                                if (callBack != null)
                                    callBack.onFailure(msg, body);
                                break;
                            case 0:
                                // 服务器返回成功json信息
                                if (callBack != null)
                                    callBack.onSuccess(msg, body);
                                break;
                            default:
                                break;
                        }
                        // 删除simple目录下的压缩图片
                        if (file.getAbsolutePath().startsWith(OtherUtils.simpleDir)) {
                            try {
                                file.delete();
                            } catch (Exception e) {
                                YD_Log.e("image", "压缩图片删除异常" + e.getMessage());
                            }
                        }
                    }

                    @Override
                    public void onError(Call arg0, Exception e, int arg2) {
                        YD_Log.e("http", e.getMessage());
                        YD_Log.writeLog("e", "报错：" + e.getMessage());
                        if (callBack != null)
                            callBack.onError(STATE_ERROR, e);

                    }
                });
    }

    /**
     * 上传回调
     *
     * @author Cong
     */
    public interface UploadCallBack {
        /**
         * 上传过程中循环调用
         *
         * @param progress 已下载的百分比？
         * @param total    总大小
         */
        void inProgress(float progress, long total);

        /**
         * 上传完成，响应结束
         */
        void onSuccess(String msg, String body);

        /**
         * 上传出错，响应结束
         */
        void onFailure(String msg, String body);

        /**
         * 连接出错
         *
         * @param e
         */
        void onError(String code, Exception e);
    }

    /**
     * get方式请求天气Json数据（desc、status、data）,并封装为bean
     *
     * @param ctx      上下文，只接受Activity或Application上下文
     * @param url
     * @param callBack
     */
    public static void getWeather(final Context ctx, String url, final BeanCallBack callBack) {
        if (!haveNet(ctx)) {
            if (callBack != null)
                callBack.onError(STATE_NO_NET, noNetException);
            return;
        }
        OkHttpUtils.get().url(url).build().execute(new StringCallback() {
            @Override
            public void onResponse(String json, int id) {
                String msg = JsonUtils.getString(json, "desc");
                int ret = JsonUtils.getInt(json, "status");
                switch (ret) {
                    case Integer.MIN_VALUE:// json解析失败
                        if (callBack != null)
                            callBack.onFailure(ret + "", "数据解析失败", json);
                        break;
                    case 1000:// 服务器返回成功JSON信息
                        if (callBack != null)
                            callBack.onSuccess(ret + "", msg, json);
                        break;
                    default:// 服务器返回成功JSON信息
                        if (callBack != null)
                            callBack.onSuccess(ret + "", msg, json);
                        break;
                }
            }

            @Override
            public void onError(Call arg0, Exception e, int arg2) {
                // 网络连接错误
                if (callBack != null)
                    callBack.onError(STATE_ERROR, e);
            }
        });

    }

    /**
     * 判断网络是否可用
     */
    public static boolean haveNet(Context context) {
        boolean isOk = false;
        ConnectivityManager connectionManager = (ConnectivityManager) context
                .getSystemService(Context.CONNECTIVITY_SERVICE);
        NetworkInfo networkInfo = connectionManager.getActiveNetworkInfo();
        if (networkInfo != null && networkInfo.isAvailable()) {
            if (networkInfo.getType() == ConnectivityManager.TYPE_WIFI) {
                isOk = true;
                YD_Log.println("wifi可用");
            } else if (networkInfo.getType() == ConnectivityManager.TYPE_MOBILE) {
                isOk = true;
                YD_Log.println("手机网络可用");
            } else {
                YD_Log.println("网络不可用");
            }
        }
        return isOk;
    }

}
